package com.csx.saas.platform.auth.grant;

import cn.hutool.crypto.SecureUtil;
import com.csx.basic.base.R;
import com.csx.basic.cache.model.CacheKey;
import com.csx.basic.cache.repository.CacheOps;
import com.csx.basic.database.mybatis.conditions.Wraps;
import com.csx.basic.exception.code.ExceptionCode;
import com.csx.basic.jwt.model.AuthInfo;
import com.csx.basic.utils.BizAssert;
import com.csx.basic.utils.StrHelper;
import com.csx.saas.common.cache.common.TokenUserIdCacheKeyBuilder;
import com.csx.saas.platform.auth.dto.LoginParamDTO;
import com.csx.saas.platform.system.entity.SystemUser;
import com.csx.saas.platform.system.service.SystemUserService;
import org.springframework.beans.factory.annotation.Autowired;
import org.springframework.stereotype.Component;

import java.time.Duration;

import static com.csx.saas.platform.auth.grant.PasswordTokenGranter.GRANT_TYPE;

/**
 * 账号密码登录获取token
 *
 * @author ChenSongXin
 * @date 2021/2/19 15:26
 */
@Component(GRANT_TYPE)
public class PasswordTokenGranter extends AbstractTokenGranter implements TokenGranter{
    public static final String GRANT_TYPE = "password";

    @Autowired
    private SystemUserService systemUserService;
    @Autowired
    private CacheOps cacheOps;


    @Override
    public R<AuthInfo> login(LoginParamDTO loginParam) {
        if (StrHelper.isAnyBlank(loginParam.getAccount(), loginParam.getPassword())) {
            return R.fail("请输入用户名或密码");
        }
        //查询账号
        SystemUser systemUser = systemUserService.getOne(Wraps.<SystemUser>lbQ().eq(SystemUser::getAccount, loginParam.getAccount()), false);
        //账号错误
        BizAssert.notNull(systemUser,ExceptionCode.JWT_USER_INVALID);

        //验证密码
        String passwordMd5 = SecureUtil.sha256(loginParam.getPassword());
        if (!passwordMd5.equalsIgnoreCase(systemUser.getPassword())) {
            // 密码错误
            BizAssert.fail(ExceptionCode.JWT_USER_INVALID);
        }
        //校验账号状态
        if (systemUser.getState().eq("locked")) {
            String msg = "用户被禁用，请联系管理员！";
            BizAssert.fail(msg);
        }
        //创建token
        AuthInfo authInfo = this.createToken(systemUser);

        //缓存toekn到redis 否则网关无法读取
        CacheKey tokenKey = new TokenUserIdCacheKeyBuilder().key(authInfo.getToken());
        tokenKey.setExpire(Duration.ofSeconds(authInfo.getExpireMillis()));
        cacheOps.set(tokenKey, String.valueOf(authInfo.getUserId()));

        return R.success(authInfo);
    }

}
